# -*- coding: utf-8 -*-
import pandas as pd
import talib as ta
import numpy as np
import matplotlib.pyplot as plt
from fbprophet import Prophet

# df = pd.read_excel('C:\Users\skyla\Documents\GOLD.xlsx')
df = pd.read_excel(r'D:\TCFEquotes0.xlsx')
# df.tail()
df['date'] = pd.to_datetime(df['T00.CFE'], format='%Y-%m-%d')


df['close'] = df['close']
df = df[df['close'] > 0]
def plot_basic_stock_history(df, start_date, end_date, stock_name):
    stat_min = min(df['close'])
    stat_max = max(df['close'])
    stat_mean = np.mean(df['close'])
    date_stat_min = df[df['close'] == stat_min]['date']
    date_stat_min = date_stat_min[date_stat_min.index[0]]
    date_stat_max = df[df['close'] == stat_max]['date']
    date_stat_max = date_stat_max[date_stat_max.index[0]]

    plt.rcParams['font.family'] = ['sans-serif']
    plt.rcParams['font.sans-serif'] = ['SimHei']
    plt.style.use('default')
    plt.plot(df['date'],
            df['close'],
            color='r',
            linewidth=1,
            label='close')
    plt.xlabel('Time growing')
    # plt.ylabel('T.CFE Price')
    plt.ylabel('TCFE history')
    plt.title('{} history'.format(stock_name))
    plt.grid()
    plt.show()


plot_basic_stock_history(df, '2015-03-20', '2021-09-23', 'TCFE growing')

min_date = min(df['date'])
max_date = max(df['date'])

def train_model(stock_history,days=0, weekly_seasonality=True, monthly_seasonality=True):
    model = Prophet(daily_seasonality=True, weekly_seasonality=True, yearly_seasonality=True,changepoint_prior_scale=0.05)
    
    if monthly_seasonality:
        model.add_seasonality(name='monthly', period=22, fourier_order=5)
    
    model.fit(stock_history)
    future = model.make_future_dataframe(periods=days)
    future = model.predict(future)
    
    return model, future

def create_prophet_model(df, stock_name, days=0, weekly_seasonality=True, monthly_seasonality=True):
    stock_history = df[df['date'] > (max_date - pd.DateOffset(years=13))]
    model, future = train_model(stock_history, days, weekly_seasonality, monthly_seasonality)
    
    plt.style.use('default')
    fig, ax = plt.subplots(1, 1)
    fig.set_size_inches(10, 5)
    
    ax.plot(stock_history['ds'],
            stock_history['y'],
            'v-',
            linewidth=1.0,
            alpha=0.8,
            ms=1.8,
            label='Observations'
           )
    ax.plot(future['ds'],
            future['yhat'],
            'o-',
            linewidth=0.7,
            label='Modeled'
           )
    ax.fill_between(
        future['ds'].dt.to_pydatetime(),
        future['yhat_upper'],
        future['yhat_lower'],
        alpha=0.3,
        facecolor='g',
        edgecolor='k',
        linewidth=1.0,
        label='Confidence Interval'
    )
    
    plt.legend(loc=2, prop={'size':10})
    
    plt.show()
    return model, future

df['ds'] = df['date']
df['y'] = df['close']

model, future = create_prophet_model(df, 'SZ', monthly_seasonality=True, days=60)

# df['excavator_ch'] = df['excavator_ch']

#1


Upperband,middleband,lowerband = ta.BBANDS(df['close'],timeperiod=5,nbdevup=2,nbdevdn=2, matype=0)

df['upperband']=Upperband
df['middleband']=middleband
df['lowerband']=lowerband

# 指数平均
df['EMA']=ta.EMA(df['close'], timeperiod=30)
df['DEMA']=ta.DEMA(df['close'], timeperiod=30)
# 希尔伯特变化趋势线
df['HT_TRENDLINE'] = ta.HT_TRENDLINE(df['close'])
# 考夫曼自动移动平均
df['KAMA']=ta.KAMA(df['close'], timeperiod=30)
# 最简单的移动平均 SMA = MA
df['SMA'] = ta.SMA(df['close'], timeperiod=30)
# MA = ta.MA(df['close'], timeperiod=30)

# 抛物线指标： 停损点转向，利用抛物线方式，随时调整停损点位置以观察买卖点。𝑆𝐴𝑅_𝑇𝑛=𝑆𝐴𝑅_(𝑇𝑛−1)+𝐴𝐹×(𝐸𝑃_(𝑇𝑛−1)−𝑆𝐴𝑅_(𝑇𝑛−1))
df['SAR']=ta.SAR(df['high'], df['low'], 𝑎𝑐𝑐𝑒𝑙𝑒𝑟𝑎𝑡𝑖𝑜𝑛=0, 𝑚𝑎𝑥𝑖𝑚𝑢𝑚=0)

# 三重指数移动平均线，长线操作时采用本指标的讯号
df['T3']= ta.T3(df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=5, 𝑣𝑓𝑎𝑐𝑡𝑜𝑟=0)
df['TEMA']= ta.TEMA(df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=5)

# 三角移动平均线，TRIMA将对价格数据进行二次平均，而其他移动平均线只进行一次平均。也就是说，TRIMA 是平均价格的平均值。
df['TRIMA']=ta.TRIMA(df['close'], timeperiod=30)

# 移动加权平均：周期内的每个点都分配有一个乘数(对于最新数据点配以最大的乘数，然后按顺序下降)，该乘数将更改该特定数据点的权重或重要性
df['WMA']=ta.WMA(df['close'], timeperiod=30)

Upperband
df.tail()


# 动量指标

# 平均趋向指数(ADX)帮助交易者确定趋势的强度，而不是它的实际方向。
# 它可以用来发现市场是在调整还是开始一个新的趋势。
# 它和趋向指数(DMI)有关，且实际上后者包含ADX指数。
# 震荡指标在0到100之间，高数值表示强趋势，低数值表示弱趋势。它经常与趋势指标相结合。
# 价格的方向性运动DM
# TR=MAX{当日最高价和最低价之差，当日最高价和前一日收盘价之差，当日最低价和前一日收盘价之差}
# DI=DM/TR
# +DI14=+DM14/ TR14，-DI14=-DM14/ TR14。计算+DI与-DI的差值：abs（+DI14）-（-DI14））；计算+DI与-DI的和值: abs(（+DI14）+（-DI14）)
# DX =（差值/和值）*100
# 𝐴𝐷𝑋=(𝐴𝐷𝑋_([−1])×(𝑛−1)+𝐷𝑋)/𝑛
# ADXR等于当前的ADX值和n个周期前的ADX的和之后除以2，即当前ADX和之前的ADX的平均值;
df['ADX'] = ta.ADX(df['high'], df['low'], df['close'], timeperiod=14)
df['MINUSDI'] = ta.𝑀𝐼𝑁𝑈𝑆_𝐷𝐼(df['high'], df['low'], df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)
df['MINUSDM'] = ta.𝑀𝐼𝑁𝑈𝑆_𝐷𝑀(df['high'], df['low'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)
df['PLUSDI'] = ta.𝑃𝐿𝑈𝑆_𝐷𝐼(df['high'], df['low'], df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)
df['PLUSDM'] = ta.𝑃𝐿𝑈𝑆_𝐷𝑀(df['high'], df['low'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)
df['ADXR'] = ta.ADXR(df['high'], df['low'], df['close'], timeperiod=14)


# 价格振荡器指数表示两个移动平均值的差，类似MACD，只是APO在时间周期上更灵活。当APO上穿0，表示买入信号；当APO下穿0，表示卖出信号。
df['APO'] = ta.APO(df['close'], fastperiod=12, slowperiod=26, matype=0)

# 阿隆指标：该指标是通过计算自价格达到近期最高值和最低值以来所经过的期间数，
# 阿隆指标帮助预测价格趋势到趋势区域（或者反过来，从趋势区域到趋势）的变化。
# 极值0与100：当Up线达到100时，市场处于多头强势；如果维持在70-100之间，表示处于多头上升趋势；
# 如果Down线达到100时，市场处于空头强势；如果维持在70-100之间，表示处于空头下降趋势。
# 当Up线达到0时，表示多头处于极弱势，如果维持在0-30之间，表明多头处于较弱势；
# 当Down线达到0时，表示空头处于极弱势，如果维持在0-30之间，表明空头处于较弱势。
# 如果两条线同处于底部，表示处于盘整时期，无趋势。

AROONU,AROOND =ta.AROON(df['high'], df['low'], timeperiod=14)
df['AROONU'] =AROONU
df['AROOND'] =AROOND
df['AROONOSC'] = ta.AROONOSC(df['high'], df['low'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)

# 推动力平衡是一款振荡器，评估行市场上买卖双方的推动力，并在适当的时间内辨别趋势逆转。
# 该指标评估了买家和卖家推动市场资产价格达到极端水平的能力。
# 当BOP高于零轴时，它显示潜在的购买。当它低于零轴时，它表明潜在的抛售。
df['BOP'] = ta.BOP(df['open'],df['high'],df['low'],df['close'])

# 顺势指标：指导股市投资的一种中短线指标，判断股价偏离度。
# CCI指标有一个相对的技术参照区域：+100和-100。
#按照指标分析的常用思路，CCI指标的运行区间也分为三类：+100以上为超买区，-100以下为超卖区，+100到-100之间为震荡区，
# 但是该指标在这三个区域当中的运行所包含的技术含义与其它技术指标的超买与超卖的定义是不同的。
df['CCI'] = ta.CCI(df['high'],df['low'],df['close'],𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)

# 钱德动量摆动指标可以作为RSI指标的改进版本，RSI指标可以写为up/(up + down), 而CMO则是(up - down)/(up + down).
# 钱德动量摆动指标在计算公式的分子中采用上涨日和下跌日的数据（“纯动量”）。
# 作为一个通用规则，钱德把超买水平定量在+50以上，把超卖水平定量在-50以下。
# 在+50，上涨日的动量是下跌日动量的3倍；同样，在-50，下跌日的动量是上涨日动量的3倍。这些水平值可与RSI指标中的70/30相对应。
df['CMO'] = ta.CMO(df['close'],𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)

# MACD
𝑚𝑎𝑐𝑑, 𝑚𝑎𝑐𝑑𝑠𝑖𝑔𝑛𝑎𝑙, 𝑚𝑎𝑐𝑑ℎ𝑖𝑠𝑡 = ta.𝑀𝐴𝐶𝐷(df['close'], 𝑓𝑎𝑠𝑡𝑝𝑒𝑟𝑖𝑜𝑑=12, 𝑠𝑙𝑜𝑤𝑝𝑒𝑟𝑖𝑜𝑑=26, 𝑠𝑖𝑔𝑛𝑎𝑙𝑝𝑒𝑟𝑖𝑜𝑑=9)
df['macd'] = macd
df['macdsignal'] = macdsignal
df['macdhist'] = macdhist
𝑚𝑎𝑐𝑑fix, 𝑚𝑎𝑐𝑑𝑠𝑖𝑔𝑛𝑎𝑙fix, 𝑚𝑎𝑐𝑑ℎ𝑖𝑠𝑡fix = ta.𝑀𝐴𝐶𝐷𝐹𝐼𝑋(df['close'], 𝑠𝑖𝑔𝑛𝑎𝑙𝑝𝑒𝑟𝑖𝑜𝑑=9)
df['macdfix'] = macdfix
df['macdsignalfix'] = macdsignalfix
df['macdhistfix'] = macdhistfix

# MFI 资金流量指标。
# MFI指标实际是将RSI加以修改后，演变而来。RSI以成交价为计算基础；MFI指标则结合价和量，将其列入综合考虑的范围。
#可以说，MFI指标是成交量的RSI指标。
# MFI介于50－80之间且保持上升时，较适合介入；
# MFI高于80时，应注意可能会短线回调，此时不宜买入，但可持仓至其回调；
# MFI小于50，则股价走势仍弱，暂且观望。
df['MFI'] = ta.𝑀𝐹𝐼(df['high'],df['low'],df['close'],df['volume'],𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)

# 动量线（简称MOM）是表示一段时间内股价涨跌变动的比率，它将每日动量值连为曲线形成动量线。该指标属于超买超卖型指标。
# 动量线研究股价在波动过程中各种加速，减速，惯性作用以及股价由静到动或由动转静的现象，
# 根据股价波动情况围绕中心线周期性往返运动，从而反映股价波动的速度，借以判断股价的“峰顶”和“谷底”，其理论基础是价格和供需量的关系。
# 运用动量线时，通常结合动量线移动平均线使用，可以取得更好的效果。
df['MOM'] = ta.𝑀𝑂𝑀(df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=10) 

# PRO主要是比较两根快、慢MA线的比例，辅助MACD。买入信号就是PRO大于0，而卖出信号就是PRO小于0；
# PRO=𝑃𝑂%=(𝑠𝑙𝑜𝑤𝑀𝐴(𝑐𝑙𝑜𝑠𝑒)−𝑓𝑎𝑠𝑡𝑀𝐴(𝑐𝑙𝑜𝑠𝑒))/(𝑓𝑎𝑠𝑡𝑀𝐴(𝑐𝑙𝑜𝑠𝑒))
df['PRO'] = ta.𝑃𝑃𝑂(df['close'], 𝑓𝑎𝑠𝑡𝑝𝑒𝑟𝑖𝑜𝑑=12, 𝑠𝑙𝑜𝑤𝑝𝑒𝑟𝑖𝑜𝑑=26, 𝑚𝑎𝑡𝑦𝑝𝑒=0)

# Rate of change : ((price/prevPrice)-1)*100 变动率指标
# Rate of change Percentage: (price-prevPrice)/prevPrice 变动率百分比
# Rate of change ratio: (price/prevPrice) 变动率比例
# Rate of change ratio 100 scale: (price/prevPrice)*100 变动率比例 100刻度
df['ROC'] = ta.𝑅𝑂𝐶(df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=10)
df['ROCP'] = ta.𝑅𝑂𝐶𝑃(df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=10)
df['ROCR'] = ta.𝑅𝑂𝐶𝑅(df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=10)
ROCR100 = ta.𝑅𝑂𝐶𝑅100(df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=10)

# RSI 相对强弱指标
df['RSI'] = ta.𝑅𝑆𝐼(df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)

# KDJ
𝑠𝑙𝑜𝑤𝑘, 𝑠𝑙𝑜𝑤𝑑 = ta.𝑆𝑇𝑂𝐶𝐻(df['high'],df['low'],df['close'], 𝑓𝑎𝑠𝑡𝑘_𝑝𝑒𝑟𝑖𝑜𝑑=5, 𝑠𝑙𝑜𝑤𝑘_𝑝𝑒𝑟𝑖𝑜𝑑=3, 𝑠𝑙𝑜𝑤𝑘_𝑚𝑎𝑡𝑦𝑝𝑒=0, 𝑠𝑙𝑜𝑤𝑑_𝑝𝑒𝑟𝑖𝑜𝑑=3, 𝑠𝑙𝑜𝑤𝑑_𝑚𝑎𝑡𝑦𝑝𝑒=0)
df['𝑠𝑙𝑜𝑤𝑘']=𝑠𝑙𝑜𝑤𝑘
df['𝑠𝑙𝑜𝑤d']=𝑠𝑙𝑜𝑤d
𝑓𝑎𝑠𝑡𝑘, 𝑓𝑎𝑠𝑡𝑑 = ta.𝑆𝑇𝑂𝐶𝐻𝐹(df['high'],df['low'],df['close'], 𝑓𝑎𝑠𝑡𝑘_𝑝𝑒𝑟𝑖𝑜𝑑=5, 𝑓𝑎𝑠𝑡𝑑_𝑝𝑒𝑟𝑖𝑜𝑑=3, 𝑓𝑎𝑠𝑡𝑑_𝑚𝑎𝑡𝑦𝑝𝑒=0)
df['fastk']= fastk
df['fastd']= fastd
𝑓𝑎𝑠𝑡𝑘RSI, 𝑓𝑎𝑠𝑡𝑑RSI = ta.𝑆𝑇𝑂𝐶𝐻𝑅𝑆𝐼(df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14, 𝑓𝑎𝑠𝑡𝑘_𝑝𝑒𝑟𝑖𝑜𝑑=5, 𝑓𝑎𝑠𝑡𝑑_𝑝𝑒𝑟𝑖𝑜𝑑=3, 𝑓𝑎𝑠𝑡𝑑_𝑚𝑎𝑡𝑦𝑝𝑒=0)
df['fastkRSI']= fastkRSI
df['fastdRSI']= fastdRSI
# UOS 终极指标
# 𝑎_1=𝑛_1 𝑆𝑀𝐴(𝑐𝑙𝑜𝑠𝑒−𝑡𝑟𝑢𝑒𝑙𝑜𝑤)×𝑛_1; 𝑏_1=𝑛_1 𝑆𝑀𝐴(𝑡𝑟𝑢𝑒𝑟𝑎𝑛𝑔𝑒)×𝑛_1 
# 𝑎_2=𝑛_2 𝑆𝑀𝐴(𝑐𝑙𝑜𝑠𝑒−𝑡𝑟𝑢𝑒𝑙𝑜𝑤)×𝑛_2;𝑏_2=𝑛_2 𝑆𝑀𝐴(𝑡𝑟𝑢𝑒𝑟𝑎𝑛𝑔𝑒)×𝑛_2 
# 𝑎_3=𝑛_3 𝑆𝑀𝐴(𝑐𝑙𝑜𝑠𝑒−𝑡𝑟𝑢𝑒𝑙𝑜𝑤)×𝑛_3;𝑏_3=𝑛_3 𝑆𝑀𝐴(𝑡𝑟𝑢𝑒𝑟𝑎𝑛𝑔𝑒)×𝑛_3 
# 𝑈𝑂𝑆=(4×𝑎_1/𝑏_1 +2×𝑎_2/𝑏_2 +𝑎_3/𝑏_3 )/7
# UOS短线抄底：UOS上穿50；UOS短线卖顶：UOS下穿65；UOS中长期抄底：UOS上穿35；UOS中长期卖顶：UOS下穿70
df['UOS'] = ta.𝑈𝐿𝑇𝑂𝑆𝐶(df['high'],df['low'],df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑1=7, 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑2=14, 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑3=28)

# WR 威廉指标
# 研究股价的波动，通过分析股价波动变化中的峰与谷决定买卖时机。它利用振荡点来反映市场的超买超卖现象，可以预测循期内的高点与低点，从而显示出有效的买卖信号，是用来分析市场短期行情走势的技术指标。
# 高于80，即处于超卖状态，低于20，即处于超买状态
# 进入高位后，一般要回头，如果股价继续上升就产生了背离，是卖出信号。
# 进入低位后，一般要反弹，如果股价继续下降就产生了背离。W&R连续几次撞顶（底），局部形成双重或多重顶（底），是卖出（买进）的信号。
# 盘整的过程中，W&R的准确性较高，而在上升或下降趋势当中，却不能只以W&R超买超卖信号作为行情判断的依据。
df['WR'] = ta.𝑊𝐼𝐿𝐿𝑅(df['high'],df['low'],df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)

# 成交量指标

# Marc Chaikin提出的累积/派发线指标，将资金流动情况与价格行为相对比，检测市场中资金流入和流出的情况。
# 也可以叫做“收集派发摆荡指标”是一个与成交量有关的股票技术指标。
# 𝐴𝐷 = 𝐴𝐷_(−1)  +𝑣𝑜𝑙𝑢𝑚𝑒 ∗ 𝐶𝐿𝑉；𝐶𝐿𝑉 = (2×𝐶𝑙𝑜𝑠𝑒 –ℎ𝑖𝑔ℎ − 𝑙𝑜𝑤) / (ℎ𝑖𝑔ℎ − 𝐿𝑜𝑤)
#缺点：只考虑了收盘价在一定交易周期内与最高价最低价的关系，
# 没有考虑与前一个交易周期价格的关系。此外，这个指标在计算中强烈依赖收盘价，所以它不能很好的反映趋势中较小的成交量变化。

# A/D线在上升时，说明交易者在买入；A/D线在下降时，说明交易者正在卖出：
df['AD'] = ta.𝐴𝐷(df['high'],df['low'],df['close'],df['volume'])

# Chaikin震荡指标 公式：𝑓𝑎𝑠𝑡𝑝𝑒𝑟𝑖𝑜𝑑 𝐴𝐷 − 𝑠𝑙𝑜𝑤𝑝𝑒𝑟𝑖𝑜𝑑 𝐴𝐷
df['ADOSC'] = ta.𝐴𝐷𝑂𝑆𝐶(df['high'],df['low'],df['close'],df['volume'], 𝑓𝑎𝑠𝑡𝑝𝑒𝑟𝑖𝑜𝑑=3, 𝑠𝑙𝑜𝑤𝑝𝑒𝑟𝑖𝑜𝑑=10)

# 该指标通过统计交易量变动的趋势来推测股价的趋势、OBV以N字型为波动单位，
# 并且由许许多多“N”型波构成了OBV的曲线图、对一浪高于一浪的“N”型波，称其为“上升潮”（UP TIDE），至于上升潮中的下跌回落则称为“跌潮”（DOWN FIELD）。
# 𝑖𝑓 𝑐𝑙𝑜𝑠𝑒>𝑐𝑙𝑜𝑠𝑒_(−1), 𝑡ℎ𝑒𝑛 𝑂𝐵𝑉=𝑂𝐵𝑉_(−1)+𝑣𝑜𝑙𝑢𝑚𝑒, 
# 𝑒𝑙𝑠𝑒𝑖𝑓 𝑐𝑙𝑜𝑠𝑒<𝑐𝑙𝑜𝑠𝑒_(−1), 𝑡ℎ𝑒𝑛 𝑂𝐵𝑉=𝑂𝐵𝑉_(−1)−𝑣𝑜𝑙𝑢𝑚𝑒
# 当股价上升（下降），而OBV也相应地上升（下降），则可确认当前的上升（下降）趋势。
# 当股价上升（下降），但OBV并未相应地上升（下降），出现背离现象，则对目前上升（下降）趋势的认定程度要大打折扣。
# OBV可以提前告诉我们趋势的后劲不足，有反转的可能
df['OBV'] = ta.𝑂𝐵𝑉(df['close'],df['volume'])

# ATR 平均真实波幅指标
# 这一技术指标并不能直接反映价格走向及其趋势稳定性，而只是表明价格波动的程度。高的ATR往往有着高波动性，而低的ATR往往波动性较低。
# 𝑇𝑟𝑢𝑒𝐻𝑖𝑔ℎ=max⁡(𝐻𝑖𝑔ℎ𝑒𝑠𝑡ℎ𝑖𝑔ℎ_0,𝑐𝑙𝑜𝑠𝑒_(−1) ), 𝑇𝑟𝑢𝑒𝐿𝑜𝑤=min⁡(𝐿𝑜𝑤𝑒𝑠𝑡𝑙𝑜𝑤_0,𝑐𝑙𝑜𝑠𝑒_(−1) )
# 𝑇𝑅=𝑇𝑟𝑢𝑒𝐻𝑖𝑔ℎ−𝑇𝑟𝑢𝑒𝐿𝑜𝑤, 𝐴𝑇𝑅=(𝑇𝑅_(−1)×(𝑛−1)+𝑇𝑅 )/𝑛
df['ATR'] = ta.𝐴𝑇𝑅(df['high'],df['low'],df['close'], 𝑡𝑖𝑚𝑒𝑝𝑒𝑟𝑖𝑜𝑑=14)


# 周期指标

df['𝐻𝑇_𝐷𝐶𝑃𝐸𝑅𝐼𝑂𝐷'] = ta.𝐻𝑇_𝐷𝐶𝑃𝐸𝑅𝐼𝑂𝐷(df['close'])
df['𝐻𝑇_𝐷𝐶𝑃𝐻𝐴𝑆𝐸'] = ta.𝐻𝑇_𝐷𝐶𝑃𝐻𝐴𝑆𝐸(df['close'])
𝑖𝑛𝑝ℎ𝑎𝑠𝑒, 𝑞𝑢𝑎𝑑𝑟𝑎𝑡𝑢𝑟𝑒 = ta.𝐻𝑇_𝑃𝐻𝐴𝑆𝑂𝑅(df['close'])
df['inphase'] = 𝑖𝑛𝑝ℎ𝑎𝑠𝑒
df['𝑞𝑢𝑎𝑑𝑟𝑎𝑡𝑢𝑟𝑒'] = 𝑞𝑢𝑎𝑑𝑟𝑎𝑡𝑢𝑟𝑒
𝑠𝑖𝑛𝑒, 𝑙𝑒𝑎𝑑𝑠𝑖𝑛𝑒 = ta.𝐻𝑇_𝑆𝐼𝑁𝐸(df['close'])
df['sine'] = sine
df['leadsine'] = leadsine
df['𝐻𝑇_𝑇𝑅𝐸𝑁𝐷𝑀𝑂𝐷𝐸'] = ta.𝐻𝑇_𝑇𝑅𝐸𝑁𝐷𝑀𝑂𝐷𝐸(df['close'])

# 形态识别

# CDL2CROWS - Two Crows
df['CDL2CROWS'] = ta.CDL2CROWS(df['open'], df['high'],df['low'],df['close'])

# CDL3BLACKCROWS - Three Black Crows
df['CDL3BLACKCROWS'] = ta.CDL3BLACKCROWS(df['open'], df['high'],df['low'],df['close'])

# CDL3INSIDE - Three Inside Up/Down
df['CDL3INSIDE'] = ta.CDL3INSIDE(df['open'], df['high'],df['low'],df['close'])

# CDL3LINESTRIKE - Three-Line Strike
df['CDL3LINESTRIKE'] = ta.CDL3LINESTRIKE(df['open'], df['high'],df['low'],df['close'])

# CDL3OUTSIDE - Three Outside Up/Down
df['CDL3OUTSIDE'] = ta.CDL3OUTSIDE(df['open'], df['high'],df['low'],df['close'])


# CDL3STARSINSOUTH - Three Stars In The South
df['CDL3STARSINSOUTH'] = ta.CDL3STARSINSOUTH(df['open'], df['high'],df['low'],df['close'])

# CDL3WHITESOLDIERS - Three Advancing White Soldiers
df['CDL3WHITESOLDIERS'] = ta.CDL3WHITESOLDIERS(df['open'], df['high'],df['low'],df['close'])


#CDLABANDONEDBABY - Abandoned Baby
df['CDLABANDONEDBABY'] = ta.CDLABANDONEDBABY(df['open'], df['high'],df['low'],df['close'], penetration=0)

#CDLADVANCEBLOCK - Advance Block
df['CDLADVANCEBLOCK'] = ta.CDLADVANCEBLOCK(df['open'], df['high'],df['low'],df['close'])

#CDLBELTHOLD - Belt-hold
df['CDLBELTHOLD'] = ta.CDLBELTHOLD(df['open'], df['high'],df['low'],df['close'])

#CDLBREAKAWAY - Breakaway
df['CDLBREAKAWAY'] = ta.CDLBREAKAWAY(df['open'], df['high'],df['low'],df['close'])

#CDLCLOSINGMARUBOZU - Closing Marubozu
df['CDLCLOSINGMARUBOZU'] = ta.CDLCLOSINGMARUBOZU(df['open'], df['high'],df['low'],df['close'])

#CDLCONCEALBABYSWALL - Concealing Baby Swallow
df['integer'] = ta.CDLCONCEALBABYSWALL(df['open'], df['high'],df['low'],df['close'])

#CDLCOUNTERATTACK - Counterattack
df['CDLCOUNTERATTACK'] = ta.CDLCOUNTERATTACK(df['open'], df['high'],df['low'],df['close'])

#CDLDARKCLOUDCOVER - Dark Cloud Cover
df['CDLDARKCLOUDCOVER'] = ta.CDLDARKCLOUDCOVER(df['open'], df['high'],df['low'],df['close'], penetration=0)

#CDLDOJI - Doji
df['CDLDOJI'] = ta.CDLDOJI(df['open'], df['high'],df['low'],df['close'])

#CDLDOJISTAR - Doji Star
df['CDLDOJISTAR'] = ta.CDLDOJISTAR(df['open'], df['high'],df['low'],df['close'])

#CDLDRAGONFLYDOJI - Dragonfly Doji
df['CDLDRAGONFLYDOJI'] = ta.CDLDRAGONFLYDOJI(df['open'], df['high'],df['low'],df['close'])

#CDLENGULFING - Engulfing Pattern
df['CDLENGULFING'] = ta.CDLENGULFING(df['open'], df['high'],df['low'],df['close'])

#CDLEVENINGDOJISTAR - Evening Doji Star
df['CDLEVENINGDOJISTAR'] = ta.CDLEVENINGDOJISTAR(df['open'], df['high'],df['low'],df['close'], penetration=0)

#CDLEVENINGSTAR - Evening Star
df['CDLEVENINGSTAR'] = ta.CDLEVENINGSTAR(df['open'], df['high'],df['low'],df['close'], penetration=0)

#CDLGAPSIDESIDEWHITE - Up/Down-gap side-by-side white lines
df['CDLGAPSIDESIDEWHITE']= ta.CDLGAPSIDESIDEWHITE(df['open'], df['high'],df['low'],df['close'])

#CDLGRAVESTONEDOJI - Gravestone Doji
df['CDLGRAVESTONEDOJI'] = ta.CDLGRAVESTONEDOJI(df['open'], df['high'],df['low'],df['close'])

#CDLHAMMER - Hammer
df['CDLHAMMER'] = ta.CDLHAMMER(df['open'], df['high'],df['low'],df['close'])

#CDLHANGINGMAN - Hanging Man
df['CDLHANGINGMAN'] = ta.CDLHANGINGMAN(df['open'], df['high'],df['low'],df['close'])

#CDLHARAMI - Harami Pattern
df['CDLHARAMI'] = ta.CDLHARAMI(df['open'], df['high'],df['low'],df['close'])

#CDLHARAMICROSS - Harami Cross Pattern
df['CDLHARAMICROSS'] = ta.CDLHARAMICROSS(df['open'], df['high'],df['low'],df['close'])

#CDLHIGHWAVE - High-Wave Candle
df['CDLHIGHWAVE'] = ta.CDLHIGHWAVE(df['open'], df['high'],df['low'],df['close'])

#CDLHIKKAKE - Hikkake Pattern
df['CDLHIKKAKE'] = ta.CDLHIKKAKE(df['open'], df['high'],df['low'],df['close'])

#CDLHIKKAKEMOD - Modified Hikkake Pattern
df['CDLHIKKAKEMOD'] = ta.CDLHIKKAKEMOD(df['open'], df['high'],df['low'],df['close'])

#CDLHOMINGPIGEON - Homing Pigeon
df['CDLHOMINGPIGEON'] = ta.CDLHOMINGPIGEON(df['open'], df['high'],df['low'],df['close'])

#CDLIDENTICAL3CROWS - Identical Three Crows
df['CDLIDENTICAL3CROWS'] = ta.CDLIDENTICAL3CROWS(df['open'], df['high'],df['low'],df['close'])

#CDLINNECK - In-Neck Pattern
df['CDLINNECK'] = ta.CDLINNECK(df['open'], df['high'],df['low'],df['close'])

#CDLINVERTEDHAMMER - Inverted Hammer
df['CDLINVERTEDHAMMER'] = ta.CDLINVERTEDHAMMER(df['open'], df['high'],df['low'],df['close'])

#CDLKICKING - Kicking
df['CDLKICKING'] = ta.CDLKICKING(df['open'], df['high'],df['low'],df['close'])

#CDLKICKINGBYLENGTH - Kicking - bull/bear determined by the longer marubozu
df['CDLKICKINGBYLENGTH'] = ta.CDLKICKINGBYLENGTH(df['open'], df['high'],df['low'],df['close'])

#CDLLADDERBOTTOM - Ladder Bottom
df['CDLLADDERBOTTOM'] = ta.CDLLADDERBOTTOM(df['open'], df['high'],df['low'],df['close'])

#CDLLONGLEGGEDDOJI - Long Legged Doji
df['CDLLONGLEGGEDDOJI'] = ta.CDLLONGLEGGEDDOJI(df['open'], df['high'],df['low'],df['close'])

#CDLLONGLINE - Long Line Candle
df['CDLLONGLINE'] = ta.CDLLONGLINE(df['open'], df['high'],df['low'],df['close'])

#CDLMARUBOZU - Marubozu
df['CDLMARUBOZU'] = ta.CDLMARUBOZU(df['open'], df['high'],df['low'],df['close'])

#CDLMATCHINGLOW - Matching Low
df['CDLMATCHINGLOW'] = ta.CDLMATCHINGLOW(df['open'], df['high'],df['low'],df['close'])

#CDLMATHOLD - Mat Hold
df['CDLMATHOLD'] = ta.CDLMATHOLD(df['open'], df['high'],df['low'],df['close'], penetration=0)

#CDLMORNINGDOJISTAR - Morning Doji Star
df['CDLMORNINGDOJISTAR'] = ta.CDLMORNINGDOJISTAR(df['open'], df['high'],df['low'],df['close'], penetration=0)

#CDLMORNINGSTAR - Morning Star
df['CDLMORNINGSTAR'] = ta.CDLMORNINGSTAR(df['open'], df['high'],df['low'],df['close'], penetration=0)

#CDLONNECK - On-Neck Pattern
df['CDLONNECK'] = ta.CDLONNECK(df['open'], df['high'],df['low'],df['close'])

#CDLPIERCING - Piercing Pattern
df['CDLPIERCING'] = ta.CDLPIERCING(df['open'], df['high'],df['low'],df['close'])

#CDLRICKSHAWMAN - Rickshaw Man
df['CDLRICKSHAWMAN'] = ta.CDLRICKSHAWMAN(df['open'], df['high'],df['low'],df['close'])

#CDLRISEFALL3METHODS - Rising/Falling Three Methods
df['CDLRISEFALL3METHODS'] = ta.CDLRISEFALL3METHODS(df['open'], df['high'],df['low'],df['close'])

#CDLSEPARATINGLINES - Separating Lines
df['CDLSEPARATINGLINES'] = ta.CDLSEPARATINGLINES(df['open'], df['high'],df['low'],df['close'])

#CDLSHOOTINGSTAR - Shooting Star
df['CDLSHOOTINGSTAR'] = ta.CDLSHOOTINGSTAR(df['open'], df['high'],df['low'],df['close'])

#CDLSHORTLINE - Short Line Candle
df['CDLSHORTLINE'] = ta.CDLSHORTLINE(df['open'], df['high'],df['low'],df['close'])

#CDLSPINNINGTOP - Spinning Top
df['CDLSPINNINGTOP'] = ta.CDLSPINNINGTOP(df['open'], df['high'],df['low'],df['close'])

#CDLSTALLEDPATTERN - Stalled Pattern
df['CDLSTALLEDPATTERN'] = ta.CDLSTALLEDPATTERN(df['open'], df['high'],df['low'],df['close'])

#CDLSTICKSANDWICH - Stick Sandwich
df['CDLSTICKSANDWICH'] = ta.CDLSTICKSANDWICH(df['open'], df['high'],df['low'],df['close'])

#CDLTAKURI - Takuri (Dragonfly Doji with very long lower shadow)
df['CDLTAKURI'] = ta.CDLTAKURI(df['open'], df['high'],df['low'],df['close'])

#CDLTASUKIGAP - Tasuki Gap
df['CDLTASUKIGAP'] = ta.CDLTASUKIGAP(df['open'], df['high'],df['low'],df['close'])

#CDLTHRUSTING - Thrusting Pattern
df['CDLTHRUSTING'] = ta.CDLTHRUSTING(df['open'], df['high'],df['low'],df['close'])

#CDLTRISTAR - Tristar Pattern
df['CDLTRISTAR'] = ta.CDLTRISTAR(df['open'], df['high'],df['low'],df['close'])

#CDLUNIQUE3RIVER - Unique 3 River
df['CDLUNIQUE3RIVER'] = ta.CDLUNIQUE3RIVER(df['open'], df['high'],df['low'],df['close'])

#CDLUPSIDEGAP2CROWS - Upside Gap Two Crows
df['CDLUPSIDEGAP2CROWS'] = ta.CDLUPSIDEGAP2CROWS(df['open'], df['high'],df['low'],df['close'])

# CDLXSIDEGAP3METHODS - Upside/Downside Gap Three Methods
df['CDLXSIDEGAP3METHODS'] = ta.CDLXSIDEGAP3METHODS(df['open'], df['high'],df['low'],df['close'])



# CDLXSIDEGAP3METHODS 


# 2.提取特征变量和目标变量
X = df.drop(columns=['close_ch', 'T00.CFE','date','ds','close'])
y = df['close_ch']    

# 11.3.2 Z-score标准化
from sklearn.preprocessing import StandardScaler
X_new = StandardScaler().fit_transform(X)
print(X_new)  # 查看X_new


# 3.划分训练集和测试集
from sklearn.model_selection import train_test_split
X_train, X_test, y_train, y_test = train_test_split(X_new, y, test_size=0.2, random_state=123)



# 4.模型训练及搭建
from xgboost import XGBClassifier
clf = XGBClassifier(n_estimators=100, learning_rate=0.05)
clf.fit(X_train, y_train)


# **10.2.3 模型预测及评估**
y_pred = clf.predict(X_test)
print(y_pred)
a = pd.DataFrame()  # 创建一个空DataFrame
a['预测值'] = list(y_pred)
a['实际值'] = list(y_test)
a.head()

from sklearn.metrics import accuracy_score
score = accuracy_score(y_pred, y_test)
print(score)

print(clf.score(X_test, y_test))

y_pred_proba = clf.predict_proba(X_test)
print(y_pred_proba[0:5])  # 查看前5个预测的概率

from sklearn.metrics import roc_curve
fpr, tpr, thres = roc_curve(y_test, y_pred_proba[:,1])
import matplotlib.pyplot as plt
plt.plot(fpr, tpr)
plt.show()

from sklearn.metrics import roc_auc_score
score = roc_auc_score(y_test, y_pred_proba[:,1])
print(score)

print(clf.feature_importances_)

features = X.columns  # 获取特征名称
importances = clf.feature_importances_  # 获取特征重要性

importances_df = pd.DataFrame()
importances_df['特征名称'] = features
importances_df['特征重要性'] = importances
importances_df.sort_values('特征重要性', ascending=False)

# **10.2.4 模型参数调优**
from sklearn.model_selection import GridSearchCV
parameters = {'max_depth': [1, 3, 5], 'n_estimators': [50, 100, 150], 'learning_rate': [0.01, 0.05, 0.1, 0.2]}  # 指定模型中参数的范围
clf = XGBClassifier()  # 构建模型
grid_search = GridSearchCV(clf, parameters, scoring='roc_auc', cv=5)  

grid_search.fit(X_train, y_train)  # 传入数据
print(grid_search.best_params_)  # 输出参数的最优值

clf = XGBClassifier(max_depth=1, n_estimators=100, learning_rate=0.05)
clf.fit(X_train, y_train)

y_pred_proba = clf.predict_proba(X_test)
from sklearn.metrics import roc_auc_score
score = roc_auc_score(y_test, y_pred_proba[:,1])
print(score)
